package com.zen.lon.open.remote.support;

import com.zen.lon.open.proxy.ProxyAgentMethodInvoker;
import com.zen.lon.open.remote.exp.RemoteClientException;
import com.zen.lon.open.remote.metadata.RemoteClientMethodMetadata;
import com.zen.lon.open.remote.utils.ClassProviderUtils;
import java.lang.reflect.Method;
import lombok.extern.slf4j.Slf4j;

/**
 * @author ZonLen since on 2021/7/12 下午3:01
 */
@Slf4j
public class RemoteClientProxyAgentMethodInvoker implements ProxyAgentMethodInvoker {

  private RemoteClientMethodMetadata remoteClientMethodMetadata;

  /**
   * RemoteClient 代理方法调用执行方法
   */
  @Override
  public Object invoke(Class<?> remoteApiClass, Method method, Object[] args) {
    if (null == this.remoteClientMethodMetadata) {
      synchronized (RemoteClientProxyAgentMethodInvoker.class) {
        if (null == this.remoteClientMethodMetadata) {
          this.remoteClientMethodMetadata = new RemoteClientMethodMetadata(method,
              RemoteClientMetaDataReader.readProxyClass(remoteApiClass));
        }
      }
      log.info("Remote Client invoke function【{}】",
          ClassProviderUtils.functionFlag(remoteApiClass, method));
      return remoteClientMethodMetadata.execute(args);
    }
    throw new RemoteClientException(
        "【" + remoteApiClass.getName() + "】is not implements RemoteApi ");
  }

}
